﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace StringDefs.Business
{
    using StringDefs.Common;
    
    public static class Business
    {
        public enum CreditCardType{MasterCard,Visa, JCB15, JCB16, Amex, DinnersClub,Discover,enRoute};

        static int digsum(this int number)
        {
            int sum = 0;
            while (number != 0)
            {
                sum += number % 10;
                number /= 10;
            }
            return sum;
        }

        /// <summary>
        /// 
        /// </summary>
        /// <param name="ISBN"></param>
        /// <returns></returns>
        public static bool IsValidISBN(this string ISBN)
        {
            List<string> kgs = new List<string>();
            int weight = 1;
            int sum = 0;
            if (ISBN.Length == 10)
            {
                kgs = (List<string>)ISBN.NGrams(1);

                for (int i = 0; i < kgs.Count - 1; i++, weight++)
                    sum += Convert.ToInt32(kgs[i]) * weight;

                if (sum % 11 == Convert.ToInt32(kgs[kgs.Count - 1]))
                    return true;

                else
                    return false;

            }

            return false;
        }

        /// <summary>
        /// 
        /// </summary>
        /// <param name="ISBN"></param>
        /// <returns></returns>
        public static bool IsValisISBN13(this string ISBN)
        {
            List<string> kgs = new List<string>();
            int weight = 3;
            int sum = 0;
            if (ISBN.Length == 13)
            {
                kgs = (List<string>)ISBN.NGrams(1);

                for (int i = 0; i < kgs.Count - 1; i++, weight++)
                    sum += Convert.ToInt32(kgs[i]) * weight;

                if (sum % 10 == Convert.ToInt32(kgs[kgs.Count - 1]))
                    return true;

                else
                    return false;

            }

            return false;
        }
        /// <summary>
        /// This method returns true if the passed argument 
        /// is a valid SIN for a Canadian Citizen.
        /// </summary>
        /// <param name="SIN">The number which is suspected as a valid SIN</param>
        /// <returns>True or False</returns>
        public static bool IsValidSIN(this string SIN)
        {
            IList<string> kgs = SIN.NGrams(1);
            int count = 1;

            int EvenSum = 0;
            int OddSum = 0;
            //for (; kgs != NULL; kgs = kgs->next)
            foreach (string k in kgs)
            {
                if (count % 2 == 0)
                    //Find digit sum of numbers we get by multiplying the digits at 
                    //even locations.
                    EvenSum += digsum(Convert.ToInt32(k) * 2);
                else
                    OddSum += Convert.ToInt32(k);
                count++;
            }
            return (EvenSum + OddSum) % 10 == 0;
        }


        /// <summary>
        /// Checks whether the Universal Product Code "upc" is valid or not.
        /// </summary>
        /// <param name="upc"></param>
        /// <returns></returns>
        /// 
        public static bool IsValidUPC(this string upc)
        {
            IList<string> kgs = upc.NGrams(1);
            int count = 1;
            int EvenSum = 0;
            int OddSum = 0;
            foreach (string k in kgs)
            {
                if (count % 2 != 0)
                    OddSum += digsum(Convert.ToInt32(k));
                else
                    EvenSum += Convert.ToInt32(k);
                count++;
            }

            return (EvenSum + 3 * OddSum) % 10 == 0;
        }
        /// <summary>
        /// 
        /// </summary>
        /// <param name="creditCard"></param>
        /// <returns></returns>
        public static bool IsValidCreditCard(this string creditCard)
        {
            if(creditCard.Length == 13 || creditCard.Length == 14 || creditCard.Length == 15 || creditCard.Length == 16)
            {
                //5210987654321450
                int sum = 0;
                for(int i = 0;i<creditCard.Length ;i++)
                {
                    int digit = Convert.ToInt32(creditCard[i].ToString());
                    if(i%2!=0)//every other digit
                    {
                        sum +=  (digit*2).digsum();
                    }
                    else
                        sum += i;
                }
                if(sum % 10 == 0)
                    return true ;
                else
                    return false ;

            }
            else
                return false;
        }

        /// <summary>
        /// Gets the short name for a given full name. For example Arnold Anderson will result in
        /// A.A 
        /// or 
        /// A.Anderson depending on the flags
        /// 
        /// </summary>
        /// <param name="fullName">The full name that you want to be shortened</param>
        /// <param name="retainLastName">Whether to retain the last name of the full name</param>
        /// <param name="considerSalutation">Whether the name has any salutaion and if yes, then whether to preserve it or not.
        /// Consider names like Dr. John Watson, Prof. Lev Jhonshon</param>
        /// <returns></returns>
        public static string ShortName(this string fullName,bool retainLastName,bool considerSalutation)
        {
            StringBuilder shortNameBuilder = new StringBuilder();
            string[] nameTokens;
            int i;
            if (!retainLastName)
            {
                nameTokens = fullName.Split(new char[] { ' ' }, StringSplitOptions.RemoveEmptyEntries);
                
                for (i = 0; i < nameTokens.Length - 1; i++)
                {
                    shortNameBuilder.Append(nameTokens[i][0] + ".");
                }
                shortNameBuilder.Append(nameTokens[i][0]);
                return shortNameBuilder.ToString();
            }
            else
            {
                if (!considerSalutation)
                {
                    nameTokens = fullName.Split(new char[] { ' ' }, StringSplitOptions.RemoveEmptyEntries);
                    for (i = 0; i < nameTokens.Length - 1; i++)
                    {
                        shortNameBuilder.Append(nameTokens[i][0] + ".");
                    }
                    
                }
                else//retain last name and salutation
                {
                    nameTokens = fullName.Split(new char[] { ' ' }, StringSplitOptions.RemoveEmptyEntries);
                    shortNameBuilder.Append(nameTokens[0] + " ");//Adding a space after salutation
                    for (i = 1; i < nameTokens.Length - 1; i++)
                    {
                        shortNameBuilder.Append(nameTokens[i][0] + ".");
                    }
                    
                }
                shortNameBuilder.Append(nameTokens[i]);
                return shortNameBuilder.ToString();
            }
           // return string.Empty;
        }

        //public static string Format(this string phrase, string format)
        //{
        //    //phrase = 1231231234
        //    //format = (###) ###-####
            
        //}
    }
}
